package com.fengwk.user.service.impl;

import java.util.ArrayList;
import java.util.Collection;
import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.fengwk.support.code.Sequence;
import com.fengwk.support.exception.BaseException;
import com.fengwk.support.page.PageInfo;
import com.fengwk.support.util.CollectionUtils;
import com.fengwk.user.dao.UsPermissionDao;
import com.fengwk.user.dao.UsRolePermissionLinkDao;
import com.fengwk.user.face.entity.UsPermission;
import com.fengwk.user.face.entity.UsRolePermissionLink;
import com.fengwk.user.face.model.Permission;
import com.fengwk.user.face.model.Role;
import com.fengwk.user.service.PermissionService;
import com.fengwk.user.service.RoleService;

@Service
public class PermissionServiceImpl implements PermissionService {

	@Autowired
	private RoleService roleService;
	
	@Autowired
	private UsPermissionDao usPermissionDao;
	@Autowired
	private UsRolePermissionLinkDao usRolePermissionLinkDao;
	
	@Transactional
	@Override
	public Permission savePermission(String permission, String description) {
		UsPermission usPermission = usPermissionDao.findByPermission(permission);
		if (usPermission != null)
			throw new BaseException("权限[" + permission + "]已存在");
		usPermission = new UsPermission();
		usPermission.setPermissionId(Sequence.next());
		usPermission.setPermission(permission);
		usPermission.setDescription(description);
		usPermissionDao.insert(usPermission);
		return usPermissionToPermission(usPermission);
	}

	@Transactional
	@Override
	public Permission removePermission(Long permissionId) {
		UsPermission usPermission = findUsPermission(permissionId);
		if (usPermission != null) {
			usRolePermissionLinkDao.deleteByPermissionId(permissionId);
			usPermissionDao.deleteByPermissionId(permissionId);
		}
		return usPermissionToPermission(usPermission);
	}

	@Transactional
	@Override
	public Permission updatePermission(Long permissionId, String permission, String description) {
		UsPermission usPermission = findUsPermission(permissionId);
		if (usPermission != null) {
			if (permission != null) 
				usPermission.setPermission(permission);
			if (description != null) 
				usPermission.setDescription(description);
			usPermissionDao.updateByPermissionId(usPermission);
		}
		return usPermissionToPermission(usPermission);
	}
	
	@Override
	public List<Permission> listPermissionByUserId(Long userId) {
		List<Role> roleList = roleService.listRoleByUserId(userId);
		List<Long> roleIdList = CollectionUtils.toListWithTypeConvert(
				roleList, role -> role.getRoleId());
		return listPermissionByRoleIds(roleIdList);
	}
	
	@Override
	public List<Permission> listPermissionByRoleIds(Collection<Long> roleIds) {
		List<Permission> permissionList = new ArrayList<>();
		if (CollectionUtils.isNotBlank(roleIds)) {
			List<UsRolePermissionLink> usRolePermissionLinkList = usRolePermissionLinkDao.queryInRoleIds(roleIds);
			if (CollectionUtils.isNotBlank(usRolePermissionLinkList)) {
				List<Long> permissionIdList = CollectionUtils.toListWithTypeConvert(
						usRolePermissionLinkList, usRolePermissionLink -> usRolePermissionLink.getPermissionId());
				List<UsPermission> usPermissionList = usPermissionDao.queryInPermissionIds(permissionIdList);
				permissionList = usPermissionsToPermissionList(usPermissionList);
			}
		}
		return permissionList;
	}
	
	@Override
	public List<Permission> listPermissionByRoleId(Long roleId) {
		return listPermissionByRoleIds(CollectionUtils.buildList(roleId, true));
	}
	
	@Override
	public PageInfo<Permission> pagePermission(int pageNum, int pageSize) {
		PageInfo<Permission> pageInfo = new PageInfo<>(pageNum, pageSize);
		List<UsPermission> usPermissionList = usPermissionDao.page(pageInfo.queryStartRow(), pageInfo.queryPageSize());
		pageInfo.setTotal(usPermissionDao.countAll());
		pageInfo.setList(usPermissionsToPermissionList(usPermissionList));
		return pageInfo;
	}
	
	private UsPermission findUsPermission(Long permissionId) {
		UsPermission usPermission = usPermissionDao.findByPermissionId(permissionId);
		if (usPermission == null) 
			throw new BaseException("权限[" + permissionId + "]不存在");
		return usPermission;
	}
	
	private Permission usPermissionToPermission(UsPermission usPermission) {
		return CollectionUtils.getFirstFromList(
				usPermissionsToPermissionList(CollectionUtils.buildList(usPermission, true)));
	}
	
	private List<Permission> usPermissionsToPermissionList(Collection<UsPermission> usPermissions) {
		return CollectionUtils.toListWithTypeConvert(
				usPermissions, usPermission -> {
					Permission permission = new Permission();
					permission.setPermissionId(usPermission.getPermissionId());
					permission.setPermission(usPermission.getPermission());
					permission.setDescription(usPermission.getDescription());
					return permission;
				});
	}

}
